package cn.com.dhcc.turbo.service.registry;

import java.util.List;

import org.apache.log4j.Logger;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Qualifier;
import org.springframework.stereotype.Service;

import cn.com.dhcc.app.core.CM;
import cn.com.dhcc.app.core.exception.DaoException;
import cn.com.dhcc.app.core.exception.NiceException;
import cn.com.dhcc.app.core.handler.remotehandler.socket.ISendDataClient;
import cn.com.dhcc.app.core.service.Log;
import cn.com.dhcc.app.core.service.Log.LOGTYPE;
import cn.com.dhcc.app.core.tag.CommonStaticCode.SUCCESSFAIL;
import cn.com.dhcc.app.core.tag.CommonStaticCode.YESNO;
import cn.com.dhcc.app.core.util.JsonUtil;
import cn.com.dhcc.app.pub.core.consts.AppIocBean;
import cn.com.dhcc.app.pub.core.consts.NodeInfoParam;
import cn.com.dhcc.app.pub.core.util.HttpUtil;
import cn.com.dhcc.turbo.dao.registry.NodePermissionDao;
import cn.com.dhcc.turbo.entity.registry.NodeInfo;
import cn.com.dhcc.turbo.entity.registry.NodePermission;
import cn.com.dhcc.turbo.entity.registry.SynchronizeInfo;
import cn.com.dhcc.turbo.entity.registry.SynchronizeInfo.SyncOperType;
import cn.com.dhcc.turbo.entity.registry.SynchronizeInfo.SyncType;
import cn.com.dhcc.turbo.service.exch.DistributedNodeInfoService;
import cn.com.dhcc.turbo.service.registry.sync.ISyncSender;
import cn.com.dhcc.turbo.service.registry.sync.SyncCallBack;
import cn.com.dhcc.turbo.service.registry.vo.NodeRegistSyncData;
import cn.com.dhcc.turbo.service.registry.vo.RegistResult;

/**
 * 针对水资源交换平台的特殊处理管理
 * @author qiao
 * @2014-8-5 @下午5:13:30
 */
@Service
public class SzyFeatureMgr{

	private static String regionCode =  NodeInfoParam.NODE_REGION_CODE;
	@Autowired
	NodePermissionDao nodePermissionDao;
	@Autowired
	NodeInfoService nodeInfoService;
	
	
	@Autowired
	AdapterBaseService adapterBaseService;
	
	@Autowired
	NodePipelineService nodePipelineService;
	@Autowired
	DomainInfoService domainInfoService;
	
	@Autowired
	private AdapterInfoService adapterInfoService;
	@Autowired
	private DataCategoryService categoryService;
	@Autowired
	@Qualifier(AppIocBean.RMI_SENDDATA_CLIENT)
	ISendDataClient socketClient;
	@Autowired
	@Qualifier(AppIocBean.SYNC_SENDER_RMI_IMPL)
	ISyncSender syncSender;
	@Autowired
	DistributedNodeInfoService distributedNodeInfoService;
	
	private static Logger logger = Log.getLogger(LOGTYPE.SYNC);
	/**
	 * 在新的节点入库之前操作，如果失败，则注册失败，新节点不能入库
	 * @param registNode
	 */
	public RegistResult registNode(NodeInfo registNode){
		RegistResult registResult = new RegistResult();
		try {
			//先验证访问地址：
			if(!HttpUtil.checkUrl(registNode.getInstallUrl())){
				registResult.setMsg("注册失败,访问地址错误!");
				registResult.setResult(SUCCESSFAIL.FAIL);
				return registResult;
			}
			//String resp =  distributedNodeInfoService.getRmi(registNode);
			NodeInfo localeNode = nodeInfoService.getLocalNode();
			
			SynchronizeInfo synchronizeInfo = new SynchronizeInfo();
			synchronizeInfo.setFromNodeInfo(localeNode);
			synchronizeInfo.setToNodeInfo(registNode);
			synchronizeInfo.setSrcNodeInfo(localeNode);
			synchronizeInfo.setOperType(SyncOperType.INSERT.getCode());
			synchronizeInfo.setDataType(SyncType.NODE_REGIST.getCode());
			//组装数据
			NodeRegistSyncData nodeRegistSyncData = new NodeRegistSyncData();
			//nodeRegistSyncData.setAllPipeInfos(nodePipelineService.list(null));
			List<NodeInfo> allNode = nodeInfoService.list(null);
			allNode.add(registNode);
			//在注册时一次性的将需要同步给新注册节点的数据给传过去：
			//包括：所有：节点信息，域信息，系统信息，适配器信息，数据分类信息
			nodeRegistSyncData.setAllNodeInfos(nodeInfoService.list(null));
			nodeRegistSyncData.setAllDomainInfos(domainInfoService.list(null));
		//	nodeRegistSyncData.setAllSysInfos(sysInfoService.list(null));
			nodeRegistSyncData.setAllAdaterBases(adapterBaseService.list(null));
			nodeRegistSyncData.setAllAdapters(adapterInfoService.list(null));
			nodeRegistSyncData.setAllCategories(categoryService.list(null));
			nodeRegistSyncData.setRegistNode(registNode);
			synchronizeInfo.setDataContent(JsonUtil.toJson(nodeRegistSyncData));
			//开始同步
			SyncCallBack callBack = syncSender.sendData(registNode.getInstallUrl(),synchronizeInfo);
			registResult.setMsg(callBack.getMsg());
			registResult.setResult(callBack.getResult());
			
		} catch (Exception e) {
			logger.error("注册节点失败",e);
			registResult.setMsg("注册失败");
			registResult.setResult(SUCCESSFAIL.FAIL);
		}
		return registResult;
	}
	/**
	 * 当前节点是否管理节点 *****根据行政区编码判断
	 * 如果是管理节点：就能够进行节点的注册和关系的管理
	 * @param currentNode
	 * @return
	 * @throws NiceException 
	 */
	public RegistResult isManagerNode() throws NiceException{
		return isManagerNode(regionCode);
	}
	/**
	 * 是否管理节点
	 * 如果是管理节点：就能够进行节点的注册和关系的管理
	 * @param currentNode
	 * @return
	 * @throws NiceException 
	 */
	public RegistResult isManagerNode(String regionCode) throws NiceException{
		RegistResult registResult = new RegistResult();
		NodePermission nodePermission = getNodePermission(regionCode);
		if(nodePermission != null){
			if(YESNO.YES.getStatus().equals(nodePermission.getIsMgr())){
				registResult.setResult(SUCCESSFAIL.SUCCESS);
				if(nodePermission.getRegionCodesToMgr().equals("")){
					registResult.setMsg("无管理范围的节点");
				}
			}else{
				registResult.setResult(SUCCESSFAIL.FAIL);
			}
		}else{
			registResult.setResult(SUCCESSFAIL.FAIL);
		}
		return registResult;
	}
	/**
	 * 获取当前节点的管理范围内的节点列表,只有管理节点有
	 * @param currentNode
	 * @return
	 * @throws NiceException 
	 */
	public List<NodeInfo> getManagedNodes() throws NiceException{
		try {
			return nodePermissionDao.getChildNodes();
		} catch (DaoException e) {
			throw new NiceException("获取本节点节点管理范围内的节点失败",e);
		}
	}
	/**
	 * 获取当前节点的管理节点
	 * @param currentNode
	 * @return
	 * @throws NiceException 
	 */
	public NodeInfo getManagerNode() throws NiceException{
		try {
			return nodePermissionDao.getParentNode();
		} catch (DaoException e) {
			throw new NiceException("获取本节点节点的管理节点失败",e);
		}
	}
	/**
	 * 获取当前节点能够监控的节点
	 * 如果是管理节点，监控需要管理管理范围的节点
	 * 如果不是管理节点，监控只监控和它有交换关系的节点
	 * @return
	 * @throws NiceException 
	 */
	public List<NodeInfo> getMonitorNodes() throws NiceException{
		if(YESNO.YES.getStatus().equals(isManagerNode(regionCode))){
			return getManagedNodes();
		}else{
			return getRelNodes();
		}
	}
	/**
	 * 获取当前节点有交换关系的节点
	 * @return
	 */
	public List<NodeInfo> getRelNodes() {
		return null;
	}
	/**
	 * 是否能够进行交换关系的建立的验证
	 * 
	 * @param fromNode
	 * @param fromNode
	 * @return
	 */
	public boolean canCreateRel(NodeInfo fromNode,NodeInfo toNode){
		return true;
	}
	
	public NodePermission getNodePermission(String regionCode) throws NiceException{
		try {
			return  CM.getDao().getModuleById("获取节点权限信息", NodePermission.class, new Object[]{regionCode});
		} catch (DaoException e) {
			throw new NiceException("获取节点权限信息失败!");
		}
	}
}
